/**
 * 
 */
package com.oauth.google.server.service;

import javax.servlet.http.HttpServletRequest;

import org.gwtwidgets.server.spring.ServletUtils;

import com.google.gdata.client.authn.oauth.GoogleOAuthHelper;
import com.google.gdata.client.authn.oauth.GoogleOAuthParameters;
import com.oauth.common.server.beans.OAuthConfigBean;
import com.oauth.service.application.ApplicationService;
import com.oauth.service.generic.beans.OAuthServiceBean;
import com.oauth.service.global.beans.OAuthAccessToken;
import com.oauth.service.global.beans.OAuthRequestToken;

/**
 * @author asanthan
 * 
 */
public abstract class AbstractGoogleOAuthService implements GoogleOAuthService {

	protected OAuthAccessToken getAccessTokenFromDB(Long pMemberId) throws Exception {
		OAuthServiceBean token = null;
		token = getApplicationService().getToken(pMemberId, getApplicationKey());
		if (token != null) {
			return new OAuthAccessToken(token.getAccessToken(), token.getAccessTokenSecret());
		}
		return null;
	}

	protected abstract Long getApplicationKey();

	protected abstract ApplicationService getApplicationService();

	protected GoogleOAuthParameters getOAuthParameters() {
		GoogleOAuthParameters oauthParameters = new GoogleOAuthParameters();
		oauthParameters.setOAuthConsumerKey(getConsumerKey());
		oauthParameters.setOAuthConsumerSecret(getConsumerSecret());
		oauthParameters.setScope(getScope());
		return oauthParameters;
	}

	/**
	 * @return
	 */
	protected abstract String getScope();

	/**
	 * @return
	 */
	protected String getConsumerSecret() {
		return getOAuthConfigBean().getConsumerSecret();
	}

	/**
	 * @return
	 */
	protected String getConsumerKey() {
		return getOAuthConfigBean().getConsumerKey();
	}

	public OAuthAccessToken getAccessToken(OAuthRequestToken pRequestToken) throws Exception {
		GoogleOAuthParameters oauthParameters = getOAuthParameters();
		HttpServletRequest request = ServletUtils.getRequest();
		String queryString = request.getQueryString();

		getOAuthHelper().getOAuthParametersFromCallback(queryString, oauthParameters);
		oauthParameters.setOAuthToken(pRequestToken.getToken());
		oauthParameters.setOAuthTokenSecret(pRequestToken.getTokenSecret());
		// Get access token .
		String accessToken = getOAuthHelper().getAccessToken(oauthParameters);
		return new OAuthAccessToken(accessToken, oauthParameters.getOAuthTokenSecret());
	}

	public OAuthRequestToken getRequestToken() throws Exception {
		GoogleOAuthParameters oauthParameters = getOAuthParameters();
		getOAuthHelper().getUnauthorizedRequestToken(oauthParameters);
		oauthParameters.setOAuthCallback(getCallBackUrl());
		String authorizeUrl = getOAuthHelper().createUserAuthorizationUrl(oauthParameters);
		OAuthRequestToken oauthTokenBean = new OAuthRequestToken(oauthParameters.getOAuthToken(),
				oauthParameters.getOAuthTokenSecret(), authorizeUrl);
		return oauthTokenBean;
	}

	/**
	 * @return
	 */
	protected abstract GoogleOAuthHelper getOAuthHelper();

	protected abstract OAuthConfigBean getOAuthConfigBean();

	/**
	 * @return
	 */
	protected String getCallBackUrl() {
		return getOAuthConfigBean().getCallBackUrl();
	}

}
